﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.SqlClient;
using System.Security.Cryptography;
using System.Data;

namespace LANmine
{
    abstract class Login
    {
        /// <summary>
        /// This function checks user credentials against the database.
        /// </summary>
        /// <param name="user">The username of the user</param>
        /// <param name="pass">The user's password</param>
        /// <returns>boolean</returns>
        public static Boolean AuthenticateUser(String user, String pass)
        {
            DataSet ds = new DataSet();
            SqlDataAdapter da;
            Database myDb = new Database("ro");

            try
            {
                // SqlDataAdapter
                da = new SqlDataAdapter("lmUserLogin", myDb.getDbConn());
                da.SelectCommand.CommandType = CommandType.StoredProcedure;

                // Add SQL arguments
                da.SelectCommand.Parameters.Add("@UserName", SqlDbType.VarChar, 50);
                da.SelectCommand.Parameters["@UserName"].Value = user;

                da.SelectCommand.Parameters.Add("@PassHash", SqlDbType.VarChar, 50);
                da.SelectCommand.Parameters["@PassHash"].Value = HashCode(pass);

                // Fill DataSet
                da.Fill(ds, "user");

                // Check whether our query returned some values
                if (ds.Tables["user"].Rows.Count > 0)
                {
                    // Close the database connection
                    return true;
                }
                else
                {
                    // Close the database connection
                    return false;
                }
            }
            catch (Exception)
            {
                // Rethrow the exception
                throw;
            }
        }

        /// <summary>
        /// Authenticates the user against the database and fills the user object.
        /// </summary>
        /// <param name="uObj">The user object to manipulate</param>
        /// <param name="u">The user's username</param>
        /// <param name="p">The user's password</param>
        /// <returns>Boolean</returns>
        public static Boolean AuthenticateUser(User uObj, String u, String p)
        {

            DataSet ds = new DataSet();
            SqlDataAdapter da;
            Database myDb = new Database("ro");
            DataTable dt = new DataTable();

            try
            {
                // SqlDataAdapter
                da = new SqlDataAdapter("lmUserLogin", myDb.getDbConn());
                da.SelectCommand.CommandType = CommandType.StoredProcedure;

                // Add SQL arguments
                da.SelectCommand.Parameters.Add("@UserName", SqlDbType.VarChar, 50);
                da.SelectCommand.Parameters["@UserName"].Value = u;

                da.SelectCommand.Parameters.Add("@PassHash", SqlDbType.VarChar, 50);
                da.SelectCommand.Parameters["@PassHash"].Value = HashCode(p);

                // Fill DataSet
                da.Fill(ds, "user");

                // Extract DataTable
                dt = ds.Tables["user"];

                // Check whether our query returned some values
                if (dt.Rows.Count > 0)
                {
                    // Select first row (TOP 1)
                    DataRow dr = dt.Rows[0];

                    // Fill up the User Object
                    uObj.ID = Convert.ToUInt32(dr["id"].ToString());
                    uObj.UserName = dr["gebruikersnaam"].ToString();
                    uObj.LastName = dr["naam"].ToString();
                    uObj.FirstName = dr["voornaam"].ToString();
                    uObj.Paid = Convert.ToBoolean(dr["betaald"].ToString());
                    uObj.Credits = Convert.ToUInt32(dr["credits"].ToString());
                    uObj.IsStaff = Convert.ToBoolean(dr["staff"].ToString());
                    uObj.Language = dr["taal"].ToString();
                    uObj.Email = dr["email"].ToString();
                    uObj.Checkedin = Convert.ToBoolean(dr["checkedin"].ToString());

                    return true;
                }
                else
                {
                    // Close the database connection
                    return false;
                }
            }
            catch (Exception)
            {
                // Rethrow the exception
                throw;
            }
        }

        /**
         * Generate a SHA1 hash from a string
         */
        public static String HashCode(String str)
        {
            SHA1 hash = SHA1.Create();
            ASCIIEncoding encoder = new ASCIIEncoding();

            byte[] bytestr = encoder.GetBytes(str);

            return Convert.ToBase64String(hash.ComputeHash(bytestr));
        }  
    }
}
